package cn.xxstudy.blog.service

import cn.xxstudy.blog.dao.CommentRepository
import cn.xxstudy.blog.entity.Comment
import org.springframework.beans.BeanUtils
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.data.domain.Sort
import org.springframework.stereotype.Service
import java.util.*
import javax.transaction.Transactional


/**
 * 作者：xinxi on 2020/11/29 13:52
 * 包名：cn.xxstudy.blog.service
 * TODO：评论数据操作service
 */
@Service
class CommentService : ICommentService {

    @Autowired
    private lateinit var commentRepository: CommentRepository

    override fun findListCommentByBlogId(id: Long): List<Comment> {
        val sort = Sort.by("createTime")
        val listComment = commentRepository.findByBlogIdAndParentCommentNull(id, sort)
        return eachComment(listComment)
    }

    override fun saveComment(comment: Comment): Comment {
        val parentCommentId = comment.parentComment.id
        if (parentCommentId != -1L) {
            comment.parentComment = commentRepository.getOne(parentCommentId)
        } else {
            comment.parentComment = null
        }
        comment.createTime = Date()
        return commentRepository.save(comment)
    }

    @Transactional
    override fun deleteCommentByBlogId(id: Long) {
        commentRepository.deleteCommentByBlogId(id)
    }

    /**
     * 循环每个顶级的评论节点
     * @param comments
     * @return
     */
    private fun eachComment(comments: List<Comment>): List<Comment> {
        val commentsView: MutableList<Comment> = ArrayList()
        for (comment in comments) {
            val c = Comment()
            BeanUtils.copyProperties(comment, c)
            commentsView.add(c)
        }
        //合并评论的各层子代到第一级子代集合中
        combineChildren(commentsView)
        return commentsView
    }

    /**
     *
     * @param comments root根节点，blog不为空的对象集合
     * @return
     */
    private fun combineChildren(comments: List<Comment>) {
        for (comment in comments) {
            val replys1 = comment.replyComments
            for (reply1 in replys1) {
                //循环迭代，找出子代，存放在tempReplys中
                recursively(reply1)
            }
            //修改顶级节点的reply集合为迭代处理后的集合
            comment.replyComments = tempReplyList
            //清除临时存放区
            tempReplyList = ArrayList<Comment>()
        }
    }

    //存放迭代找出的所有子代的集合
    private var tempReplyList: MutableList<Comment> = ArrayList()

    /**
     * 递归迭代，剥洋葱
     * @param comment 被迭代的对象
     * @return
     */
    private fun recursively(comment: Comment) {
        tempReplyList.add(comment) //顶节点添加到临时存放集合
        if (comment.replyComments.size > 0) {
            val replys = comment.replyComments
            for (reply in replys) {
                tempReplyList.add(reply)
                if (reply.replyComments.size > 0) {
                    recursively(reply)
                }
            }
        }
    }
}